﻿local function print(text)
	DEFAULT_CHAT_FRAME:AddMessage("|c0033CCFF"..text);
end

-------------------------------------------------------------------------
--   PROCESS FUNCTION
--
--   Updaes the bars fromthe roster data, using the specified functions
--
-------------------------------------------------------------------------
local canTarget = nil
local inCombat = nil

local test = 0

function OZ_ProcessBars(n)
--DEFAULT_CHAT_FRAME:AddMessage("|c0033CCFF".."  Process: "..n);
	local i
	local config = OZ_Config[n]
	local window = OZ_Windows[n]
	canTarget = 1
	inCombat = InCombatLockdown()
	if test>0 then
		if test > 2 then
			test = test - 1
		else
			inCombat = 1
		end
	end

	if window.moveable or not inCombat then
		-- Step 1, fill bars from input
		OZ_InputFunctions[config.input].pFunction(n)

		-- Step 2, apply filtering
		OZ_FilterBars(n);
		if(OZ_Input.nBars > 40)then
			OZ_Input.nBars = 40
		end

		-- Now get buffs/debuffs for inputs
		OZ_ShowPlayerBuffs(n)

		if( OZ_Input.nBars == 0)then
			OZ_Bars[n].nBars = 0
			return
		end

		-- Step 3: Sort
		OZ_InitSortTable(OZ_Input.nBars)
		local scale = nil
		if(config.sort1 > 0) then
			OZ_SortFunctions[config.sort1].pFunction (n)
			scale = 100
		end
		if(config.sort2 > 0) then
			if(scale)then
				-- We have already done one sort.
				-- IF this sort is either 'bar length' or 'status' we must apply the 1st sort
				-- (status & bar length are floats, so simply scaling doesnt work)
				-- Having these as the 2nd sort doesntmakea huge amount of sense anyway,
				-- so we hopefully only sort once per window (if at all)
				-- Note that the doublesort also only works as the merge-sort is a 'stable' sort
				if(config.sort2 <= 2)then
					OZ_DoSort()
					scale = nil
				end
			end
			OZ_SortFunctions[config.sort2].pFunction (n, scale)
			OZ_DoSort()
		elseif(scale)then
			OZ_DoSort() -- sort1 hasnt been applied and there is no sort2
		end
		OZ_FinaliseSort(n)

		for i = 1,OZ_Bars[n].nBars do
			OZ_Bars[n].bar[i].header = nil
		end

		-- Step 4: Format
		OZ_ColourFunctions[config.colour].pFunction (n)

		-- Step 7: Add Bar Headers
		for i = 1,OZ_Bars[n].nBars do
			OZ_ShowBuffs(n,i)
		end

		if( config.heading[2] > 0 ) then
			OZ_HeadingFunctions[config.heading[2]].pFunction (n)
		end

		if( config.heading[1] > 0 ) then
			OZ_HeadingFunctions[config.heading[1]].pFunction (n)
		end
	else
		OzRaid_UpdateTargetData() -- Need this checked for aggro glow
		-- Secure frames - cant change contents during lockdown
		if OZ_Bars[n].nBars == 0 then
			return
		end
		if OZ_InputFunctions[config.input].combat then
			OZ_InputFunctions[config.input].combat (OZ_Bars[n])
		end
		OZ_UpdatePlayerBuffs(n)
		-- Step 4: Format
		OZ_ColourFunctions[config.colour].pFunction (n)

		-- Step 7: Add Bar Headers
		for i = 1,OZ_Bars[n].nBars do
			OZ_ShowBuffs(n,i)
		end
		-- Dont alter headings for locked bars in combat (screws everything up!)
	end
end

function OzAddTexture( parent, childname, layer )
	local name = parent:GetName()..childname
	parent:CreateTexture( name, layer )
	return getglobal( name )
end


-- Function to set up bar size/colours based on the data in OZ_Bars
function OZ_SetBars(n)
	local row
	local h = 0
	local config = OZ_Config[n]
	local window = OZ_Windows[n]
    local bars = OZ_Bars[n]
	local a = config.maxBars
    local rm, rt = OZ_RaidRoster.member,OZ_RaidRoster.target

	if( bars.nBars < a ) then
		a = bars.nBars
	end

	local barWidth = config.width - 10
	local barHeight = config.barHeight
	

	local showMark
	if( a > 0) then
		for row = 1,a do
			local currBar = bars.bar[row]
			local currFrame = OZ_GetBar(window,row)
			local unit = currBar.unit
			local p = currBar.roster
			local isClose = 1
			local text, value, bValK, bValN, c
			local tr,tg,tb = 1,1,1
			local nr,ng,nb = 1,1,1
			local br,bg,bb = 1,1,1
			local col = currBar.colour
			local player,class,aggro;

			if( p>0) then
				player = rm[p]
            end
	
			if(config.valuePos)then
				if(config.valueType == 1)then
					if(config.bigVals) then
						bValK = floor(currBar.current*0.001)
						bValN = currBar.current - (bValK * 1000)
						if(bValK < 1)then
							bValK = nil
						end
					else
						value = currBar.current
					end
				elseif(config.valueType == 2)then
					config.bigVals = nil
					if currBar.value and currBar.value>0.01 then
						value = string.format("%3.0d%%", currBar.value * 100)
					else
						value = ""
					end
				elseif(config.valueType == 3)then
					if(currBar.current < currBar.max) then
						c = currBar.max-currBar.current
						if(config.bigVals) then
							bValK = floor(c*0.001)
							bValN = c - (bValK * 1000)
							if(bValK < 1)then
								bValK = nil
							else
								bValK = "-"..bValK
							end
						else
							value = "-"..(c)
						end
						tr = 1;
						tg = 0.2;
						tb = 0.2;
					end
				end
			end

			currBar.icon = nil
			if( player) then
				-- This bar is a PLAYER
				text = player.name
				local ns = config.nameStyle
				if OZ_NAME_FORMATS[ns] and player.formatted[ns] then
					text = player.formatted[ns]
				end

				isClose = player.range
                if config.classNames then
                    class = player.fileName;
--print("Class = "..class)
                end

				if( not player.online )then
					if( config.nameOnStatus )then
						nr = 0.7
						ng = 0.7
						nb = 0.7
                        class = nil
					end
					currBar.value = 1.0
					col.r = 0.4
					col.g = 0.4
					col.b = 0.4
					isClose = nil

					value = ""
					bValK = nil
					bValN = nil
				elseif( player.isDead )then
					if( config.nameOnStatus )then
						nr = 1
						ng = 0
						nb = 0
                        class = nil
					end
					currBar.value = 1.0
					col.r=0.3
					col.g=0.2
					col.b=0.2
					if( UnitIsGhost(player.unit ) )then
						player.icon = "Interface\\Icons\\Ability_Vanish"
					end

					value = ""
					bValK = nil
					bValN = nil
				else
					aggro = player.hasAggro
				end
                if(currBar.debuff)then
                    currBar.icon = currBar.debuff
                else
                    currBar.icon = player.icon                
                end
                
                if (OZ_CurrentTime - OZ_ReadyCheckTimer) < 5.0 then
                    if player.isReady==0 then
                        currBar.icon = "Interface\\RAIDFRAME\\ReadyCheck-NotReady"
                    elseif  not player.isReady then
                        currBar.icon = "Interface\\RAIDFRAME\\ReadyCheck-Waiting"
                    else
                        currBar.icon = "Interface\\RAIDFRAME\\ReadyCheck-Ready"
                    end
                else
                    OZ_ReadyCheckActive = 0
                end
					
			elseif( currBar.target > 0 ) then

				-- This bar is a mob
				local target = rt[currBar.target]
				text = target.name
				isClose = target.range
				player = target
                if config.classNames then
                    class = target.class;
                end
                if(currBar.debuff)then
                    currBar.icon = currBar.debuff
                else
                    currBar.icon = target.icon
                end
			else
				-- Aggregated
				text = currBar.class
				currBar.icon = nil
			end
			currBar.name = text
             
            if class and OZ_CLASS_COLOURS[class] then
                nr = OZ_CLASS_COLOURS[class].r
                ng = OZ_CLASS_COLOURS[class].g
                nb = OZ_CLASS_COLOURS[class].b
            end
            
			if( currBar.icon ~= currFrame.iconVal )then
				if( currBar.icon )then
					currFrame.icon:SetWidth( OZ_Config[n].buttonSize )
					if(currFrame.iconTex:GetTexture() ~= currBar.icon)then
						currFrame.iconTex:SetTexture( currBar.icon )
					end
				else
					currFrame.icon:SetWidth( 0.1 )
				end
				currFrame.iconVal = currBar.icon
			end

			-- mark current target
			if unit and UnitIsUnit("target",unit) then
				window.marker:SetPoint("CENTER",currFrame.barFrame,"LEFT",0,0)
				showMark = true
			end
			
			if currFrame.barFrame.unit ~= unit then
				if not window.moveable and not inCombat then
					currFrame.barFrame:SetAttribute("unit",unit)
					currFrame.barFrame.unit = unit
				end
			end

			if( (currBar.nameRed ~= nr) or
				(currBar.nameGreen ~= ng) or
				(currBar.nameBlue ~= nb) )then
				currFrame.nameText:SetTextColor( nr,ng,nb )
			end
			if(currFrame.nameVal ~= text)then
				currFrame.nameText:SetText( text )
				currFrame.nameVal = text
			end

			if(currFrame.valueVal ~= value)then
				if(value)then
					if(not currFrame.value:IsVisible())then
						currFrame.value:Show()
					end
					currFrame.valueText:SetText( value )
					currFrame.valueText:SetTextColor( tr,tg,tb )
				elseif(currFrame.value:IsVisible())then
					currFrame.value:Hide()
				end
				currFrame.valueVal = value
			end

		if (currFrame.bValK ~= bValK) or (currFrame.bValN ~= bValN) then
			if( bValN )then
				if(not currFrame.bValue:IsVisible())then
					currFrame.bValue:Show()
				end
				if bValK then
					bValN = string.format("%03d",bValN);
				end

				currFrame.bValueN:SetText( bValN )
				currFrame.bValueK:SetText( bValK )
				currFrame.bValueN:SetTextColor( tr,tg,tb )
				currFrame.bValueK:SetTextColor( tr,tg,tb )

				local wN = currFrame.bValueN:GetStringWidth()
				local wK = currFrame.bValueK:GetStringWidth()
				currFrame.bValueN:SetWidth( currFrame.bValueN:GetStringWidth() + 4 )
				currFrame.bValueK:SetWidth( currFrame.bValueK:GetStringWidth() + 4 )
			elseif(currFrame.bValue:IsVisible())then
				currFrame.bValue:Hide()
			end
			currFrame.bValK = bValK
			currFrame.bValN = bValN
		end

			local w = barWidth*currBar.value
			if( w > barWidth ) then
				w = barWidth
			elseif( w < 0.1 ) then
				w = 0.1
			end
			currFrame.bar:SetWidth( w );
			if(config.barTexture)then
				currFrame.bar:SetTexCoord(0,currBar.value * 0.75,0,1)
			end

			currFrame.bar:SetVertexColor(	col.r,
											col.g,
											col.b );

			local newA = 1
			if config.rangeFade and currBar.unit and not isClose then
				newA = config.fadeAlpha
			else
				newA = 1
			end

			currFrame.bar:SetAlpha(newA)
			if config.fadeName then
				currFrame.nameText:SetAlpha(newA)
			else
				currFrame.nameText:SetAlpha(1)
			end				
-- aggro = 1
			if( aggro and not config.hideGlow )then
				currFrame.glow:SetAlpha(aggro)
				if(not currFrame.glow:IsVisible())then
					currFrame.glow:Show()
				end
			else
				if(currFrame.glow:IsVisible())then
					currFrame.glow:Hide()
				end
			end

			-- EVIL BODGE to show mana bars!
			local showMana
			if config.showMana and player then
				if player.power == 0 then
					if player.maxMana > 0 and player.online then
						showMana = player.mana / player.maxMana
					else
						showMana = nil
					end
				end
			end
			if showMana then
                local mf = currFrame.manaFrame
				if not mf then
					mf = OzAddTexture(currFrame.barFrame, "mana", "OVERLAY")
                    currFrame.manaFrame = mf
					mf:SetVertexColor( 0.2, 0.2, 1.0 )
					if config.barTexture then
						mf:SetTexture( config.barTexture )
					else
						mf:SetTexture( "Interface\\Addons\\OzRaid\\bar1" )					
					end
					mf:SetPoint("BOTTOMLEFT", currFrame.barFrame )
				end
				mf:SetHeight(barHeight * 0.33)
				local w = barWidth * showMana
				if w > barWidth then w = barWidth end
				mf:SetWidth(w+0.1)
				mf:SetTexCoord(0,showMana * 0.75,0,1)
				mf:Show()
				mf:SetAlpha(newA)
			else
				if currFrame.manaFrame then
					currFrame.manaFrame:Hide()
				end
			end

			if (currBar.header) then
				if(currFrame.headerVal ~= currBar.header) then
					currFrame.headerVal = currBar.header
					currFrame.frame:SetHeight(barHeight + config.textSize + 2)
					currFrame.header:SetHeight(config.textSize + 2)
					currFrame.headerText:SetText(currBar.header)
				end
				if(not currFrame.headerText:IsVisible())then
					currFrame.headerText:Show()
					currFrame.header:Show()
				end
				h = h + barHeight + config.textSize + 4
			else
				if(currFrame.headerVal)then
					currFrame.headerVal = nil
					currFrame.frame:SetHeight(barHeight + config.barGap)
					currFrame.header:SetHeight(config.barGap + 0.01)
				end
				if(currFrame.headerText:IsVisible())then
					currFrame.headerText:Hide()
				end
				h = h + barHeight + config.barGap
			end

			if(not currFrame.frame:IsVisible())then
				currFrame.frame:Show()
			end

		end
	end
	if window.marker:IsVisible() then
		if not showMark then
			window.marker:Hide()
		end
	elseif showMark then
		window.marker:Show()
	end
	
	local prev = 40 --window.maxBars or 40
	if a < prev then
		for row = a+1,prev do
			local bar = window.bar[row]
			if bar then
				currFrame = bar.frame
				if(currFrame:IsVisible())then
					currFrame:Hide()
				end
			end
		end
	end
	OZ_Bars[n].nBars = a;
	window.MaxBars = a
	
	if( h<config.barHeight * config.minBars )then
		h = config.barHeight * config.minBars
	end
	h = h + 16
	if(not config.hideTitle)then
		h = h + config.titleHeight
	end
	if( h < 20)then
		h = 20
	end
	if window.moveable or not inCombat then
		window.frame:SetHeight(h)
	end
end



function OZ_FormatRow(n,i)
	local row = "OzRaid_Frame"..n.."TableRow"..i.."BarFrame"
	local config = OZ_Config[n]
	local window = OZ_Windows[n]
	local currBar = OZ_GetBar(window,i)
	
	-- Setup name & Icon position
	currBar.icon:ClearAllPoints()
	currBar.icon:SetWidth(config.buttonSize)
	currBar.icon:SetHeight(config.buttonSize)
	currBar.iconVal = 1

	currBar.name:ClearAllPoints()
	currBar.name:SetHeight(config.barHeight)

	if(config.namePos == 1)then
		-- Names positioned ON the bars
		currBar.icon:SetPoint("LEFT",row)
		currBar.name:SetPoint("LEFT", row.."Icon", "RIGHT")
		currBar.name:SetWidth(config.width - config.buttonSize - 10)
		currBar.nameText:SetJustifyH("LEFT")
	elseif(config.namePos == 2)then
		-- Names positioned to the LEFT of the bars
		currBar.icon:SetPoint("RIGHT",row,"LEFT", -6, 0)
		currBar.name:SetPoint("RIGHT", row.."Icon", "LEFT", -6, 0)
		currBar.name:SetWidth(config.width)
		currBar.nameText:SetJustifyH("RIGHT")
	elseif(config.namePos == 3)then
		-- Names positioned to the RIGHT of the bars
		currBar.icon:SetPoint("LEFT",row,"RIGHT", 4, 0)
		currBar.name:SetPoint("LEFT", row.."Icon", "RIGHT")
		currBar.name:SetWidth(config.width)
		currBar.nameText:SetJustifyH("LEFT")
	else
		-- Names positioned CENTRED ON the bars
		currBar.icon:SetPoint("LEFT",row)
		if(config.valuePos == 3)then
			currBar.name:SetPoint("CENTER",row,"CENTER",-16,0)
			currBar.name:SetWidth(config.width - 40)
		else
			currBar.name:SetPoint("CENTER",row,"CENTER",-6,0)
			currBar.name:SetWidth(config.width - 8)
		end
		currBar.nameText:SetJustifyH("CENTER")
	end

	-- Now setup buff positions
	local j
	for j=1,OZ_MAX_BUFFS do
		currBar.buff[j]:ClearAllPoints()
	end

	local size = config.buttonSize
	for j=1,OZ_MAX_BUFFS do
		currBar.buff[j]:SetWidth(0.1)
		currBar.buff[j]:SetHeight(size)
		currBar.buff[j]:EnableMouse(true)
		currBar.buffVal[j] = "invalid"
	end
	if(config.buffSize == 1)then
		if(config.buffPos == 1)then
			-- Buffs on the bar, right hand side, tiling left
			currBar.buff[1]:SetPoint("RIGHT",row)
			currBar.buff[2]:SetPoint("RIGHT", row.."Buff1","LEFT")
			currBar.buff[3]:SetPoint("RIGHT", row.."Buff2","LEFT")
			currBar.buff[4]:SetPoint("RIGHT", row.."Buff3","LEFT")
			currBar.buff[5]:SetPoint("RIGHT", row.."Buff4","LEFT")
			currBar.buff[6]:SetPoint("RIGHT", row.."Buff5","LEFT")
			currBar.buff[1]:EnableMouse(nil)
			currBar.buff[2]:EnableMouse(nil)
			currBar.buff[3]:EnableMouse(nil)
			currBar.buff[4]:EnableMouse(nil)
			currBar.buff[5]:EnableMouse(nil)
			currBar.buff[6]:EnableMouse(nil)
		elseif(config.buffPos == 2)then
			-- Buffs to the left of the bar, tiling left
			currBar.buff[1]:SetPoint("RIGHT", row,"LEFT", -6, 0)
			currBar.buff[2]:SetPoint("RIGHT", row.."Buff1","LEFT")
			currBar.buff[3]:SetPoint("RIGHT", row.."Buff2","LEFT")
			currBar.buff[4]:SetPoint("RIGHT", row.."Buff3","LEFT")
			currBar.buff[5]:SetPoint("RIGHT", row.."Buff4","LEFT")
			currBar.buff[6]:SetPoint("RIGHT", row.."Buff5","LEFT")
		else
			-- Buffs to the right of the bar, tiling right
			currBar.buff[1]:SetPoint("LEFT", row,"RIGHT",6,0)
			currBar.buff[2]:SetPoint("LEFT", row.."Buff1","RIGHT")
			currBar.buff[3]:SetPoint("LEFT", row.."Buff2","RIGHT")
			currBar.buff[4]:SetPoint("LEFT", row.."Buff3","RIGHT")
			currBar.buff[5]:SetPoint("LEFT", row.."Buff4","RIGHT")
			currBar.buff[6]:SetPoint("LEFT", row.."Buff5","RIGHT")
		end
	else
		size = config.buttonSize * 0.5
		if(config.buffPos == 1)then
			-- Buffs on the bar, right hand side, Square arrangement
			currBar.buff[1]:SetPoint("TOPRIGHT",row)
			currBar.buff[2]:SetPoint("BOTTOMRIGHT",row)
			currBar.buff[3]:SetPoint("RIGHT", row.."Buff1","LEFT")
			currBar.buff[4]:SetPoint("RIGHT", row.."Buff2","LEFT")
			currBar.buff[5]:SetPoint("RIGHT", row.."Buff3","LEFT")
			currBar.buff[6]:SetPoint("RIGHT", row.."Buff4","LEFT")
			currBar.buff[1]:EnableMouse(nil)
			currBar.buff[2]:EnableMouse(nil)
			currBar.buff[3]:EnableMouse(nil)
			currBar.buff[4]:EnableMouse(nil)
			currBar.buff[5]:EnableMouse(nil)
			currBar.buff[6]:EnableMouse(nil)
		elseif(config.buffPos == 2)then
			-- Buffs to the left of the bar, Square arrangement
			currBar.buff[1]:SetPoint("TOPRIGHT", row,"TOPLEFT",-6,0)
			currBar.buff[2]:SetPoint("BOTTOMRIGHT", row,"BOTTOMLEFT",-6,0)
			currBar.buff[3]:SetPoint("RIGHT", row.."Buff1","LEFT")
			currBar.buff[4]:SetPoint("RIGHT", row.."Buff2","LEFT")
			currBar.buff[5]:SetPoint("RIGHT", row.."Buff3","LEFT")
			currBar.buff[6]:SetPoint("RIGHT", row.."Buff4","LEFT")
		else
			-- Buffs to the right of the bar, Square arrangement
			currBar.buff[1]:SetPoint("TOPLEFT", row,"TOPRIGHT", 6, 0)
			currBar.buff[2]:SetPoint("BOTTOMLEFT", row,"BOTTOMRIGHT", 6, 0)
			currBar.buff[3]:SetPoint("LEFT", row.."Buff1","RIGHT")
			currBar.buff[4]:SetPoint("LEFT", row.."Buff2","RIGHT")
			currBar.buff[5]:SetPoint("LEFT", row.."Buff3","RIGHT")
			currBar.buff[6]:SetPoint("LEFT", row.."Buff4","RIGHT")
		end
	end
	
	if(currBar.headerVal) then
		currBar.frame:SetHeight(config.barHeight + config.textSize + 4)
		currBar.header:SetHeight(config.textSize + 4)
	else
		currBar.frame:SetHeight(config.barHeight + config.barGap)
		currBar.header:SetHeight(config.barGap + 0.01)
	end

	Oz_FormatValues(currBar, config, row)

	-- Set texture
	if(config.barTexture)then
		if(currBar.barTexture ~= currBar.bar:GetTexture())then
			currBar.bar:SetTexture(config.barTexture)
		end
	else
		if(currBar.barTexture ~= "Interface\\TargetingFrame\\UI-StatusBar")then
			currBar.bar:SetTexture("Interface\\TargetingFrame\\UI-StatusBar")
		end
	end

	window.frame:SetWidth(config.width)
end

function Oz_FormatValues(currBar,config,row)
	-- Now set the number positions
	if(config.valuePos)then
		local vFrame = currBar.value
		local tFrame = currBar.valueText
		local yOff = 0
		local xOff = 0
		if config.bigVals then
			vFrame = currBar.bValue
			tFrame = currBar.bValueN
			currBar.value:Hide()
--			yOff = -(config.numSize * 0)
--			if(currBar.headerVal)then
--				yOff = yOff - (config.textSize * 0.25)
--			end
			xOff = 8
		else
			currBar.bValue:Hide()
		end

		vFrame:ClearAllPoints()
		local align
		if(config.valuePos == 1)then
			vFrame:SetPoint("RIGHT", row,"LEFT", xOff-16, yOff)
			tFrame:SetJustifyH("RIGHT")
		elseif(config.valuePos == 2)then
			vFrame:SetPoint("CENTER", row,"CENTER",xOff,yOff)
			tFrame:SetJustifyH("CENTER")
		elseif(config.valuePos == 3)then
			vFrame:SetPoint("RIGHT", row,"RIGHT", xOff-6, yOff)
			tFrame:SetJustifyH("RIGHT")
		else
			vFrame:SetPoint("LEFT", row,"RIGHT", xOff+6, yOff)
			tFrame:SetJustifyH("LEFT")
		end
		if(config.valueType == 3)then
			-- DEFICIT gets hidden/shown when drawn
			vFrame:Hide()
		else
			vFrame:Show()
		end
		currBar.value:SetHeight(16)
		currBar.value:SetWidth(100)
	else
		currBar.value:Hide()
		currBar.bValue:Hide()
	end
end

function OZ_ShowBuffs(n,i)
	local config = OZ_Config[n]
	local size = OZ_Config[n].buttonSize
	if(OZ_Config[n].buffSize ~= 1)then
		size = size * 0.5
	end
    local size2 = size*1.25
    
	local window = OZ_Windows[n]
	local currFrame = OZ_GetBar(window,i)
	local currBar = OZ_Bars[n].bar[i]
	local j
	for	j=1,OZ_MAX_BUFFS do
        local bbuff = currBar.buffs[j]
		local buffPath = bbuff[0]
        local cfb = currFrame.buff[j]
		if(currFrame.buffVal[j] ~= buffPath)then
			if(buffPath)then
				currFrame.buffTex[j]:SetTexture(buffPath)
                if bbuff[4] then
                    cfb:SetAlpha(1)
                    cfb:SetWidth(size2)
                    cfb:SetHeight(size2)
                else
                    cfb:SetAlpha(0.6)
                    cfb:SetWidth(size)
                    cfb:SetHeight(size)                    
                end
                --currFrame.buffTex[j]:SetScale(0.5)
				cfb:Show()
			else
				cfb:SetWidth(0.1)
				cfb:Hide()
			end
			currFrame.buffVal[j] = buffPath
		end

		-- Set cooldown timer if available
		-- This needs to be done every time in case the buff has been re-applied
		-- but the position has not changed
		if buffPath then
--			if currBar.buffDur[j] and currBar.buffTimes[j] and not config.hideTimers then
			if bbuff[2] and bbuff[3] and not config.hideTimers then
				CooldownFrame_SetTimer( currFrame.buffCool[j], GetTime() - (bbuff[2] - bbuff[3]), bbuff[2], 1 )
			else
				currFrame.buffCool[j]:Hide();
			end
		end
	end

--	if(OZ_Config[n].hideIcon)then
--		currBar.icon = nil
--	end

	-- Set debuffed!
    local cc = currBar.colour
	if currBar.debuff then
		if not currBar.noncure then
			if( config.barDebuffCol )then
				cc.r = 1
				cc.g = 0
				cc.b = 1
			end
			if not config.showDebuffIcon then
				currBar.debuff = nil
			end
		end
	elseif UnitIsCharmed(currBar.unit) and config.barDebuffCol then
		cc.r = 1
		cc.g = 0
		cc.b = 0
			-- make bar BIG to be visible
		currBar.value = 1.0
	end
end

function OZ_NullFunc()
end

function OZ_UpdatePlayerBuffs(n)
	local i,j,curr,removed,texture,num,type,key,value,dur,time,mine
	local _, name, debuffs
	local status = OZ_Config[n].filter.status
	local bars = OZ_Bars[n]
	local config = OZ_Config[n]

	-- test for a curable debuff (the 1 at the end can be a '0' to show all debuffs)
	if(config.allDebuffs) then
		debuffs = 1
	end

	i = 1
	while(i <= bars.nBars) do
		local buffList,BuffFunc,DebuffFunc
		local bar = bars.bar[i]
		curr = 0
		removed = nil

		if(bar.roster > 0)then
			buffList = config.buffsPlayer
			BuffFunc = OZ_Buff
			DebuffFunc = OZ_Debuff
		elseif(bar.target > 0)then
			buffList = config.buffsMob
			BuffFunc = OZ_Debuff
			DebuffFunc = OZ_Buff
		end

		bar.debuff = nil
		bar.noncure = true
		bar.nBuffs = 0

		if bar.unit and BuffFunc then
			name,_,texture, num, type = DebuffFunc(bar.unit, 1, 1)
			-- Ignore dreamless sleep
			if name and string.find(name,"reamless") then
				name = nil;
				texture = nil;
			end

			if(texture)then
				bar.debuff = texture
				bar.noncure = false
			else
				-- Check for player debuffs (power word shield one specifically)
				for j = 1,8 do
					name,_,texture, num, type = DebuffFunc(bar.unit, j)
					if name and string.find(name,"reamless") then
                        name = nil;
                        texture = nil;
                    end

					if texture then
						if buffList[texture] or debuffs then		
							bar.debuff = texture
							break
						end
					elseif not texture then
						break
					end
				end
			end

			for j = 1,24 do
				name,_,texture,num,dur,time,mine = BuffFunc(bar.unit, j)

				if(texture) then
					local watched = buffList[texture]
					if watched then
						-- This buff is a watched buff - yay!
						curr = curr + 1
                        local score = 5-watched[1]
                        if mine then score = score - 10; end
                        OZ_SortMap[curr*2 - 1] = score
--						OZ_SortMap[curr*2 - 1] = 5-watched[1]
						OZ_SortMap[curr*2] = texture

						watched[2] = name
						watched[3] = dur
						watched[4] = time
					end
				else
					break
				end
			end
		end
		if(curr > 0)then
			-- We found some buffs to show...
			if(curr > 1)then
				OZ_internalMergeSort2(curr * 2)
				if(curr > OZ_MAX_BUFFS)then
					curr = OZ_MAX_BUFFS
				end
			end

			-- Now add them to bars...
			for j = 1,curr do
				local a = OZ_SortMap[j*2]
                if not bar.buffs[j] then bar.buffs[j] = {}; end
                local bbuffs = bar.buffs[j];
                bbuffs[0]	 = a
                bbuffs[1]	 = buffList[ a ][2]
                bbuffs[2]	 = buffList[ a ][3]
                bbuffs[3]	 = buffList[ a ][4]
                if OZ_SortMap[j*2 - 1] < 0 then bbuffs[4]=1 else bbuffs[4]=nil end
--				bar.buffs[j]	 = a
--				bar.buffNames[j] = buffList[ a ][2]
--				bar.buffDur[j]	 = buffList[ a ][3]
--				bar.buffTimes[j] = buffList[ a ][4]
			end
		end
		if(curr < OZ_MAX_BUFFS) then
			for j = curr+1,OZ_MAX_BUFFS do
                if not bar.buffs[j] then bar.buffs[j] = {}; end
				bar.buffs[j][0] = nil
--				bar.buffNames[j] =nil
			end
		end
		i = i + 1
	end
end

OZ_CurrentTooltipBar = nil
OZ_CurrentTooltipFrame = nil
OZ_CurrentTooltipCurrent = nil

function OZ_ToolTipHide()
	OZ_CurrentTooltipBar = nil
	OZ_CurrentTooltipFrame = nil
	OZ_CurrentTooltipCurrent = nil
	OzTooltip:Hide()
end

function OZ_FormatTime( time )
    local sec = mod(time, 60)
    local min = time * 0.016666
    if(min < 60)then
        return string.format("%dm %ds",min,sec)
    else
        local hour = time * 0.000277777
        return string.format("%dh %dm",hour,min)
    end
end

function OZ_ToolTip(frame)
	if not frame then frame = this end
	local n = frame:GetParent():GetParent():GetParent():GetID()
	local config = OZ_Config[n]
   
	if(config.tooltips)then
		local i = frame:GetParent():GetID()
		local bar = OZ_Bars[n].bar[i]
		local unit = bar.unit
		local player
		if(bar.roster > 0)then
			-- It is a player...
			player = OZ_RaidRoster.member[bar.roster]
            local pname = player.name;
          
            -- Hide tooltips in combat (they are a bit scary when needing to heal!)
            if UnitAffectingCombat("player") then
                -- Micro tips :)
                local cd = oRA.modules.OptionalCooldown;
                if cd then
                    if cd.db and cd.db.realm and cd.db.realm.cooldowns then
                        local cdt = cd.db.realm.cooldowns[pname];
                        if cdt then
                            cdt = cdt - time();
                            OzTooltip:SetOwner(frame, "ANCHOR_CURSOR");
                            OzTooltip:ClearLines()                            
                            if player.fileName == "WARLOCK" then
                                OzTooltip:AddLine("Soulstone up in: " .. OZ_FormatTime(cdt));
                            elseif player.fileName == "DRUID" then
                                OzTooltip:AddLine("Rebirth up in: " .. OZ_FormatTime(cdt));
                            elseif player.fileName == "SHAMAN" then
                                OzTooltip:AddLine("Reincarnation up in: " .. OZ_FormatTime(cdt));
                            end
                            OzTooltip:SetScale(0.6);
                            OzTooltip:Show();
                        else
                        end
                    end
                end
                return
            end

            -- NEW - check if we are over a buff, & show buff tooltip instead
            if(config.buffPos == 1)then
                local currBar = OZ_Windows[n].bar[i]
                local j

                OZ_CurrentTooltipBar = currBar
                OZ_CurrentTooltipFrame = frame
                OZ_CurrentTooltipCurrent = nil

                for j=1,OZ_MAX_BUFFS do
                    if MouseIsOver(currBar.buff[j]) then
                        OZ_BuffTooltip(currBar.buff[j]);
                        OZ_CurrentTooltipCurrent = currBar.buff[j];
                        return
                    end
                end
            end

			OzTooltip:SetOwner(frame, "ANCHOR_CURSOR");
			OzTooltip:ClearLines()
			OzTooltip:SetUnit(unit)
			if(CT_RA_Stats) then
				local stats = CT_RA_Stats[pname];
				if(stats)then
					-- We have CTRaid stats!
					-- This code taken straight from CTRaid
					-- (No sense reinventing the wheel after all)
					local version = stats;
					if ( version ) then
						version = version["Version"];
					end
					if ( not version ) then
						if ( not stats or not stats["Reporting"] ) then
							OzTooltip:AddLine("No CTRA Found", 0.7, 0.7, 0.7);
						else
							OzTooltip:AddLine("CTRA <1.077", 1, 1, 1);
						end
					else
						OzTooltip:AddLine("CTRA " .. version, 1, 1, 1);
					end

					if ( player.offline ) then
						-- Um... do this outside
					elseif ( stats and stats["FD"] ) then
						if ( stats["FD"] < 360 ) then
							OzTooltip:AddLine("Dying in " .. CT_RA_FormatTime(360-stats["FD"]));
						end
					elseif ( stats and stats["Dead"] ) then
						if ( stats["Dead"] < 360 and not UnitIsGhost(unit) ) then
							OzTooltip:AddLine("Releasing in " .. CT_RA_FormatTime(360-stats["Dead"]));
						else
							OzTooltip:AddLine("Dead for " .. CT_RA_FormatTime(stats["Dead"]));
						end
					end
					if ( stats and stats["Rebirth"] and stats["Rebirth"] > 0 ) then
						OzTooltip:AddLine("Rebirth up in: " .. CT_RA_FormatTime(stats["Rebirth"]));
					elseif ( stats and stats["Reincarnation"] and stats["Reincarnation"] > 0 ) then
						OzTooltip:AddLine("Ankh up in: " .. CT_RA_FormatTime(stats["Reincarnation"]));
					elseif ( stats and stats["Soulstone"] and stats["Soulstone"] > 0 ) then
						OzTooltip:AddLine("Soulstone up in: " .. CT_RA_FormatTime(stats["Soulstone"]));
					end
				end
            elseif oRA and oRA.modules then
                local cd = oRA.modules.OptionalCooldown;
                --OZDumpTable(oRA.modules);
                if cd then
                    if cd.db and cd.db.realm and cd.db.realm.cooldowns then
                        local cdt = cd.db.realm.cooldowns[pname];
                        if cdt then
                            cdt = cdt - time();
                            if cdt>0 then
                                if player.fileName == "WARLOCK" then
                                    OzTooltip:AddLine("Soulstone up in: " .. OZ_FormatTime(cdt));
                                elseif player.fileName == "DRUID" then
                                    OzTooltip:AddLine("Rebirth up in: " .. OZ_FormatTime(cdt));
                                elseif player.fileName == "SHAMAN" then
                                    OzTooltip:AddLine("Reincarnation up in: " .. OZ_FormatTime(cdt));
                                end
                            end
                         end
                    end
                end
            else
                print("no cooldown")
			end
            local diff,sec,min,hour
			if(player.dead)then	OzTooltip:AddLine("Dead for: "..OZ_FormatTime(GetTime() - player.dead)); end
			if(player.afk)then	OzTooltip:AddLine("AFK for: "..OZ_FormatTime(GetTime() - player.afk)); end
			if(player.offline)then	OzTooltip:AddLine("Offline for: "..OZ_FormatTime(GetTime() - player.offline)); end
            OzTooltip:SetScale(0.6);
			OzTooltip:Show();
          
		end
	end
end

function OZ_BuffTooltip(frame)
	local left,secure,secs,mins
	if not frame then frame = this end
	local n = frame:GetParent():GetParent():GetParent():GetParent():GetID()

--DEFAULT_CHAT_FRAME:AddMessage("|c0033CCFF".."  Buff Tooltip...");
--	if InCombatLockdown() then return end

	if(OZ_Config[n].tooltips)then
		OzTooltip:SetOwner(frame, "ANCHOR_CURSOR");
		OzTooltip:ClearLines()


		local i = frame:GetParent():GetParent():GetID()
		local bar = OZ_Bars[n].bar[i]
		local unit = bar.unit
		local id = frame:GetID()
		if(unit)then
			-- It is a player...
			local buff = bar.buffs[id]
			if(buff[0])then
				local buffName = buff[1]

				if(CT_RA_Stats)then
					local stats = CT_RA_Stats[bar.name];
					if(stats)then
						if(not stats["Buffs"][buffName] and (buffName == "Mark of the Wild") )then
							buffName = "Gift of the Wild"
						end
					end

					if ( stats and stats["Buffs"][buffName] and stats["Buffs"][buffName][2] ) then
						left = stats["Buffs"][buffName][2];
						if ( stats["Reporting"] and ( stats["Version"] or 0 ) >= 1.38 ) then
							secure = 1;
						end
					end
				end
				if not left then
					-- Ok, CTRaid not helping, lets see if we can get the time...
					local buffId
					local name,_,time
					for buffId = 1,32 do
--DEFAULT_CHAT_FRAME:AddMessage("|c0033CCFF".."  Buff Tooltip, checking buff "..buffId);
						name,_,_,_,_,time = OZ_Buff(unit,buffId)
						if name == buffName then
							if time then
								left = floor(time)
								secure = 1
--DEFAULT_CHAT_FRAME:AddMessage("|c0033CCFF".."  FOUND: Time left = "..time);
							end
							break
						end
					end
				end
				if ( left ) then
					local str;
					if ( left >= 60 ) then
						secs = mod(left, 60);
						mins = (left-secs)/60;
					else
						mins = 0;
						secs = left;
					end
					if ( mins < 0 ) then mins = "00"; elseif ( mins < 10 ) then mins = "0" .. mins; end
					if ( secs < 0 ) then secs = "00"; elseif ( secs < 10 ) then secs = "0" .. secs; end
					if(secure)then
						OzTooltip:SetText(buffName .. " (" .. mins .. ":" .. secs .. ")");
					else
						OzTooltip:SetText(buffName .. " (" .. mins .. ":" .. secs .. "?)");
					end
					OzTooltip:Show();
					return
				end
				if( buffName ) then
					OzTooltip:SetText(buffName);
                    OzTooltip:SetScale(0.6);
                    OzTooltip:Show();
				end
			end
		end
	end
end